/* Copyright (c) 2025 Beijing Semidrive Technology Corporation
 * SPDX-License-Identifier: Apache-2.0
 *
 * Licensed under the Apache License, Version 2.0 (the "License");
 * you may not use this file except in compliance with the License.
 * You may obtain a copy of the License at
 *
 * http://www.apache.org/licenses/LICENSE-2.0
 *
 * Unless required by applicable law or agreed to in writing, software
 * distributed under the License is distributed on an "AS IS" BASIS,
 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
 * See the License for the specific language governing permissions and
 * limitations under the License.
 */

/**
 * @file  Canif.c
 * @brief Semidrive. AUTOSAR 4.3.1 MCAL Canif Driver.
 */

#ifdef __cplusplus
extern "C" {
#endif

#include "Mcal.h"
#include "CanIf_Types.h"
#include "CanIf_Cbk.h"
#include "Can_Cfg.h"
#include "debug.h"

/* Version and Check Begin */
/* Version Info Begin */
#define CANIF_C_VENDOR_ID    0x8C
#define CANIF_C_AR_RELEASE_MAJOR_VERSION    4
#define CANIF_C_AR_RELEASE_MINOR_VERSION    3
#define CANIF_C_AR_RELEASE_REVISION_VERSION 1
#define CANIF_C_SW_MAJOR_VERSION    1
#define CANIF_C_SW_MINOR_VERSION    0
#define CANIF_C_SW_PATCH_VERSION    0
/* Version Info End */

/* Version Check Begin */
#if !defined(DISABLE_MCAL_ASR_VER_CHECK)
#if ((CANIF_C_AR_RELEASE_MAJOR_VERSION != MCAL_H_AR_RELEASE_MAJOR_VERSION)\
    || (CANIF_C_AR_RELEASE_MINOR_VERSION != MCAL_H_AR_RELEASE_MINOR_VERSION)\
    || (CANIF_C_AR_RELEASE_REVISION_VERSION != MCAL_H_AR_RELEASE_REVISION_VERSION))
#error "Opps, CanIf.c and Mcal.h AutoSAR version not match!"
#endif
#endif  /* !DISABLE_MCAL_ASR_VER_CHECK */
#if !defined(DISABLE_MCAL_SW_VER_CHECK)
#if ((CANIF_C_SW_MAJOR_VERSION != MCAL_H_SW_MAJOR_VERSION)\
    || (CANIF_C_SW_MINOR_VERSION != MCAL_H_SW_MINOR_VERSION)\
    || (CANIF_C_SW_PATCH_VERSION != MCAL_H_SW_PATCH_VERSION))
#error "Opps, CanIf.c and Mcal.h Software version not match!"
#endif
#endif  /* !DISABLE_MCAL_SW_VER_CHECK */
#if !defined(DISABLE_MCAL_ASR_VER_CHECK)
#if ((CANIF_C_AR_RELEASE_MAJOR_VERSION != CANIF_TYPES_H_AR_RELEASE_MAJOR_VERSION)\
    || (CANIF_C_AR_RELEASE_MINOR_VERSION != CANIF_TYPES_H_AR_RELEASE_MINOR_VERSION)\
    || (CANIF_C_AR_RELEASE_REVISION_VERSION != CANIF_TYPES_H_AR_RELEASE_REVISION_VERSION))
#error "Opps, CanIf.c and CanIf_Types.h AutoSAR version not match!"
#endif
#endif  /* !DISABLE_MCAL_ASR_VER_CHECK */
#if !defined(DISABLE_MCAL_SW_VER_CHECK)
#if ((CANIF_C_SW_MAJOR_VERSION != CANIF_TYPES_H_SW_MAJOR_VERSION)\
    || (CANIF_C_SW_MINOR_VERSION != CANIF_TYPES_H_SW_MINOR_VERSION)\
    || (CANIF_C_SW_PATCH_VERSION != CANIF_TYPES_H_SW_PATCH_VERSION))
#error "Opps, CanIf.c and CanIf_Types.h Software version not match!"
#endif
#endif  /* !DISABLE_MCAL_SW_VER_CHECK */
#if !defined(DISABLE_MCAL_ASR_VER_CHECK)
#if ((CANIF_C_AR_RELEASE_MAJOR_VERSION != CANIF_CBK_H_AR_RELEASE_MAJOR_VERSION)\
    || (CANIF_C_AR_RELEASE_MINOR_VERSION != CANIF_CBK_H_AR_RELEASE_MINOR_VERSION)\
    || (CANIF_C_AR_RELEASE_REVISION_VERSION != CANIF_CBK_H_AR_RELEASE_REVISION_VERSION))
#error "Opps, CanIf.c and CanIf_Cbk.h AutoSAR version not match!"
#endif
#endif  /* !DISABLE_MCAL_ASR_VER_CHECK */
#if !defined(DISABLE_MCAL_SW_VER_CHECK)
#if ((CANIF_C_SW_MAJOR_VERSION != CANIF_CBK_H_SW_MAJOR_VERSION)\
    || (CANIF_C_SW_MINOR_VERSION != CANIF_CBK_H_SW_MINOR_VERSION)\
    || (CANIF_C_SW_PATCH_VERSION != CANIF_CBK_H_SW_PATCH_VERSION))
#error "Opps, CanIf.c and CanIf_Cbk.h Software version not match!"
#endif
#endif  /* !DISABLE_MCAL_SW_VER_CHECK */
/* Version Check End */
/* Version and Check End */
/*PRQA S 1751,2996  EOF*/
uint32 t_cnt = 0;
uint32 r_cnt = 0;

uint32 CanFD1_SendCounter = 0;
uint32 CanFD1_ReceiveCounter = 0;
uint32 CanFD5_SendCounter = 0;
uint32 CanFD5_ReceiveCounter = 0;
uint32 CanFD2_SendCounter = 0;
uint32 CanFD2_ReceiveCounter = 0;
uint32 CanFD6_SendCounter = 0;
uint32 CanFD6_ReceiveCounter = 0;
uint32 CanFD3_ExampleCounter = 0;
uint32 VCan1_SendCounter = 0;
uint32 VCan1_ReceiveCounter = 0;
uint32 CanFD8_SendCounter = 0;
uint32 CanFD8_ReceiveCounter = 0;
uint32 CanFD11_SendCounter = 0;
uint32 CanFD11_ReceiveCounter = 0;
uint32 VCan2_SendCounter = 0;
uint32 VCan2_ReceiveCounter = 0;
uint32 CanFD9_SendCounter = 0;
uint32 CanFD9_ReceiveCounter = 0;
uint32 CanFD7_SendCounter = 0;
uint32 CanFD7_ReceiveCounter = 0;
uint32 CanFD3_SendCounter = 0;
uint32 CanFD3_ReceiveCounter = 0;
uint32 CanFD4_SendCounter = 0;
uint32 CanFD4_ReceiveCounter = 0;

FUNC(void, CANIF_CODE) CanIf_TxConfirmation
(
    VAR(PduIdType, AUTOMATIC) CanTxPduId
)
{
    PRINT("%s[line %d]: Tx complemetes for pdu id 0x%x\n", __FUNCTION__, __LINE__, CanTxPduId);
    t_cnt++;

    if ((/* CAN_HTH_5 */5 == CanTxPduId) || (/* CAN_FD1_HTH1 */127 == CanTxPduId) ||
            (/* CAN_FD1_HTH2 */128 == CanTxPduId) || (/* CAN_HTH_4 */4 == CanTxPduId) ||
            (/* CAN_HTH_5 */14 == CanTxPduId)
       )
    {
        CanFD1_SendCounter++;
    }

    if ((/* CAN_HTH_1 */1 == CanTxPduId) || (/* CAN_HTH_3 */3 == CanTxPduId) ||
            (/* CAN_HTH_1 */1 == CanTxPduId) || (/* CAN_HTH_3 */3 == CanTxPduId) ||
            (/* CAN_HTH_6 */16 == CanTxPduId)
       )
    {
        CanFD5_SendCounter++;
        CanFD3_ExampleCounter++;
    }

    if (/* CAN_HTH_7 */7 == CanTxPduId)
    {
        CanFD2_SendCounter++;
    }

    if (/* CAN_HTH_9 */9 == CanTxPduId)
    {
        CanFD6_SendCounter++;
    }

    if (/* CAN_HTH_21 */21 == CanTxPduId)
    {
        CanFD8_SendCounter++;
    }

    if (/* CAN_HTH_25 */25 == CanTxPduId)
    {
        CanFD9_SendCounter++;
    }
    if ((/* CAN_HTH_5 */5 == CanTxPduId)||(92 == CanTxPduId)||(93 == CanTxPduId))
    {
        CanFD3_SendCounter++;
    }
    if (/* CAN_HTH_25 */19 == CanTxPduId)
    {
        CanFD4_SendCounter++;
    }
    if (/* CAN_HTH_25 */21 == CanTxPduId)
    {
        CanFD1_SendCounter++;
    }
}

#if defined(CFG_NATIVE_CAN_ROUTING)
extern void Can_MsgRouting(const Can_HwType *HwInfo, const PduInfoType *PduInfo);
#endif  /* CFG_NATIVE_CAN */
/* this api used for can_routing demo now, user need porting it to AUTOSAR PudR layer */

#if defined(AUTOSAR_VERSION_403)
FUNC(void, CANIF_CODE) CanIf_RxIndication
(
    VAR(Can_HwHandleType, CANIF_APPL_DATA) hoh,
    VAR(Can_IdType, CANIF_APPL_DATA) CanId,
    VAR(PduLengthType, CANIF_APPL_DATA) SduLength,
    P2VAR(uint8, AUTOMATIC, AUTOSAR_COMSTACKDATA) SduDataPtr
)
{
    //PRINT("%s[line %d]: Rx frame by HRH %d\n", __FUNCTION__, __LINE__, hoh);
    //PRINT("\t Frame ID = 0x%x\n", CanId);
    //PRINT("\t Frame length = %d\n", SduLength);

    // for (uint8 i = 0; i < SduLength; i++)
    // {
    //     PRINT("\t Frame data[%d] = 0x%2x\n", i, SduDataPtr[i]);
    // }
}
#else
FUNC(void, CANIF_CODE) CanIf_RxIndication
(
    P2CONST(Can_HwType, AUTOMATIC, CANIF_APPL_DATA) Mailbox,
    P2CONST(PduInfoType, AUTOMATIC, CANIF_APPL_DATA) PduInfoPtr
)
{
    PRINT("%s[line %d]: Rx frame by controller %d HRH %d\n", __FUNCTION__, __LINE__,
          Mailbox->ControllerId, Mailbox->Hoh);
    PRINT("\t Frame ID = 0x%x\n", Mailbox->CanId);
    PRINT("\t Frame length = %d\n", PduInfoPtr->SduLength);

    // #include "bootloader.h"
    // BL_GetCanFrameData(Mailbox, PduInfoPtr);
    for (uint8 i = 0; i < PduInfoPtr->SduLength; i++)
    {
        PRINT("\t Frame data[%d] = 0x%2x\n", i, PduInfoPtr->SduDataPtr[i]);
    }

    r_cnt++;

    if ((((0x327) | (0U << 30)) == Mailbox->CanId) || (((0x328) | (0U << 30)) == Mailbox->CanId) ||
            (((0x329) | (0U << 30)) == Mailbox->CanId) || (((0x32A) | (0U << 30)) == Mailbox->CanId) ||
            (((0x32B) | (0U << 30)) == Mailbox->CanId) || (((0x32C) | (0U << 30)) == Mailbox->CanId) ||
            (((0x32D) | (0U << 30)) == Mailbox->CanId) || (((0x32E) | (0U << 30)) == Mailbox->CanId) ||
            (((0x666) | (0U << 30)) == Mailbox->CanId) || (((0x888) | (0U << 30)) == Mailbox->CanId) ||
            (((0x138) | (0U << 30)) == Mailbox->CanId) || (((0x139) | (0U << 30)) == Mailbox->CanId) ||
            (((0x140) | (0U << 30)) == Mailbox->CanId) || (((0x141) | (0U << 30)) == Mailbox->CanId) ||
            (((0x142) | (0U << 30)) == Mailbox->CanId) || (((0x143) | (0U << 30)) == Mailbox->CanId) ||
            (((0x144) | (0U << 30)) == Mailbox->CanId) || (((0x145) | (0U << 30)) == Mailbox->CanId) ||
            (((0x400) | (1U << 30)) == Mailbox->CanId) || (((0x401) | (1U << 30)) == Mailbox->CanId) ||
            (((0x402) | (1U << 30)) == Mailbox->CanId) || (((0x403) | (1U << 30)) == Mailbox->CanId) ||
            (((0x141) | (1U << 30)) == Mailbox->CanId) || (((0x142) | (1U << 30)) == Mailbox->CanId) ||
            (((0x143) | (1U << 30)) == Mailbox->CanId) || (((0x144) | (1U << 30)) == Mailbox->CanId) ||
            (((0x17171710) | (3U << 30)) == Mailbox->CanId) || (((0x17171711) | (3U << 30)) == Mailbox->CanId)
            ||
            (((0x17171712) | (3U << 30)) == Mailbox->CanId) || (((0x17171713) | (3U << 30)) == Mailbox->CanId)
            ||
            (((0x18181810) | (2U << 30)) == Mailbox->CanId) || (((0x18181811) | (2U << 30)) == Mailbox->CanId)
            ||
            (((0x18181812) | (2U << 30)) == Mailbox->CanId) || (((0x18181812) | (2U << 30)) == Mailbox->CanId)
            ||
            (((0x18181813) | (2U << 30)) == Mailbox->CanId) || (((0x18181814) | (2U << 30)) == Mailbox->CanId)
            ||
            (((0x18181815) | (2U << 30)) == Mailbox->CanId) || (((0x18181816) | (2U << 30)) == Mailbox->CanId)
            ||
            (((0x18181815) | (3U << 30)) == Mailbox->CanId) || (((0x18181816) | (3U << 30)) == Mailbox->CanId)
       )
    {
        CanFD1_ReceiveCounter++;
        CanFD3_ReceiveCounter++;
    }

    if ((((0x111) | (0U << 30)) == Mailbox->CanId) || (((0x112) | (0U << 30)) == Mailbox->CanId) ||
            (((0x113) | (0U << 30)) == Mailbox->CanId) || (((0x114) | (0U << 30)) == Mailbox->CanId) ||
            (((0x121) | (0U << 30)) == Mailbox->CanId) || (((0x122) | (0U << 30)) == Mailbox->CanId) ||
            (((0x123) | (0U << 30)) == Mailbox->CanId) || (((0x124) | (0U << 30)) == Mailbox->CanId) ||
            (((0x131) | (1U << 30)) == Mailbox->CanId) || (((0x132) | (1U << 30)) == Mailbox->CanId) ||
            (((0x133) | (1U << 30)) == Mailbox->CanId) || (((0x134) | (1U << 30)) == Mailbox->CanId) ||
            (((0x111) | (1U << 30)) == Mailbox->CanId) || (((0x112) | (1U << 30)) == Mailbox->CanId) ||
            (((0x113) | (1U << 30)) == Mailbox->CanId) || (((0x114) | (1U << 30)) == Mailbox->CanId) ||
            (((0x18181810) | (3U << 30)) == Mailbox->CanId) || (((0x18181812) | (3U << 30)) == Mailbox->CanId)
            ||
            (((0x18181811) | (3U << 30)) == Mailbox->CanId) || (((0x18181813) | (3U << 30)) == Mailbox->CanId)
       )
    {
        CanFD5_ReceiveCounter++;
        VCan1_ReceiveCounter++;
    }

    if ((((0x18171613) | (3U << 30)) == Mailbox->CanId)
            || (((0x18171614) | (3U << 30)) == Mailbox->CanId))
    {
        CanFD2_ReceiveCounter++;
    }

    if ((((0x18171611) | (3U << 30)) == Mailbox->CanId)
            || (((0x18171612) | (3U << 30)) == Mailbox->CanId))
    {
        CanFD6_ReceiveCounter++;
    }
    if((((0x41) | (0U << 30)) == Mailbox->CanId)||(((0x444) | (0U << 30)) == Mailbox->CanId)||(((0x445) | (0U << 30)) == Mailbox->CanId))
    {
        CanFD6_ReceiveCounter++;
    }
    if((((0x82) | (1U << 30)) == Mailbox->CanId))
    {
        CanFD11_ReceiveCounter++;
    }
    if((((0x222) | (1U << 30)) == Mailbox->CanId))
    {
        VCan2_ReceiveCounter++;
    }
    if((((0x427) | (0U << 30)) == Mailbox->CanId))
    {
        CanFD4_ReceiveCounter++;
    }
    if((((0x333) | (0U << 30)) == Mailbox->CanId))
    {
        CanFD1_ReceiveCounter++;
    }
}
#endif


#if defined(AUTOSAR_VERSION_421) || defined(AUTOSAR_VERSION_403)
FUNC(void, CANIF_CODE) CanIf_ControllerModeIndication
(
    VAR(uint8, AUTOMATIC) ControllerId,
    VAR(CanIf_ControllerModeType, AUTOMATIC) ControllerMode
)
#else
FUNC(void, CANIF_CODE) CanIf_ControllerModeIndication
(
    VAR(uint8, AUTOMATIC) ControllerId,
    VAR(Can_ControllerStateType, AUTOMATIC) ControllerMode
)
#endif
{
    // PRINT("%s: Controller %d ControllerMode %d\n", __FUNCTION__, ControllerId, ControllerMode);
}

FUNC(void, CANIF_CODE) CanIf_ControllerBusOff
(
    VAR(uint8, AUTOMATIC) ControllerId
)
{
    PRINT("%s: Controller %d bus off\n", __FUNCTION__, ControllerId);
}

FUNC(Std_ReturnType, CAN_CODE) CanIf_TriggerTransmit
(
    VAR(PduIdType, AUTOMATIC) TxPduId,
    P2VAR(PduInfoType, AUTOMATIC, CANIF_APPL_DATA) PduInfoPtr
)
{
    PRINT("%s: Fill Tx data for HTH 0x%x\n", __FUNCTION__, TxPduId);
    PduInfoPtr->SduLength = 7U;
    /*uses little endian format. */
    PduInfoPtr->SduDataPtr[3] = 0x11U;
    PduInfoPtr->SduDataPtr[2] = 0x22U;
    PduInfoPtr->SduDataPtr[1] = 0x33U;
    PduInfoPtr->SduDataPtr[0] = 0x44U;
    PduInfoPtr->SduDataPtr[7] = 0x55U;
    PduInfoPtr->SduDataPtr[6] = 0x66U;
    PduInfoPtr->SduDataPtr[5] = 0x77U;

    return E_OK;
}

#ifdef __cplusplus
}
#endif
